package com.noassertions.web;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.Enumeration;

import javax.servlet.http.HttpServletRequest;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.iscreen.ValidationException;
import org.iscreen.ValidationServiceWrapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

import com.noassertions.data.DAOInterface;
import com.noassertions.domain.Comment;
import com.noassertions.domain.User;
import com.noassertions.services.LuceneIndexer;

@Controller
public class CommentController {

	protected final Log log = LogFactory.getLog(getClass());
	private DAOInterface dao;
	private ValidationServiceWrapper commentValidator;
    private final LuceneIndexer luceneIndexer;

	@Autowired
	public CommentController(DAOInterface dao, ValidationServiceWrapper fitValidator, ValidationServiceWrapper commentValidator, LuceneIndexer luceneIndexer) {
		this.dao = dao;
		this.commentValidator = commentValidator;
        this.luceneIndexer = luceneIndexer;
	}  

	@RequestMapping(value = "/comment/{fitid}", method = RequestMethod.GET)
	public String getFit(@PathVariable Integer fitid, Model model)
	{
		ArrayList comments = dao.getCommentsByFitId(fitid);
    	Collections.reverse(comments);
		model.addAttribute("comments", comments);
		log.debug("Found " + comments.size() + " for fitid " + fitid);
		return "comment";
	}

	@RequestMapping(value = "/comment", method = RequestMethod.POST)
	public String createNewFit(HttpServletRequest request, Model model) throws Exception
	{
		Comment comment = new Comment();

		Enumeration namesEnum = request.getParameterNames();
		while (namesEnum.hasMoreElements()) {
			String name = (String)namesEnum.nextElement();
			String value = request.getParameter(name);
			if (name.equals("commenter")) {
				if (value == null || "".equals(value)) {
					comment.setCommenter("Anonymous");
				} else {
					// TODO: we should be getting emailaddress from user table linked by userid in comment table and not storing emailaddress in comment
					User user = dao.getUserByemailAddress(value);
					comment.setCommenter(user.getFirstname() + " " + user.getLastname());
				}
			}
			if (name.equals("fitid")) {comment.setFitid(Integer.valueOf(value));}
			if (name.equals("comment")) {comment.setComment(value);}

			// a bit of spam checking (this field is hidden in our form and should be empty)
			if (name.equals("bread")) {
				if (!"".equals(value)) {
					log.debug("Possible spam, bread field was not empty");
					return "home";
				}
			}			
			
			log.debug("comment received: "  + name + " = " + value);
		}


		// TODO provide mechanism for filter comments?
		comment.setDisplay(true);
		Date now = new Date();
		comment.setCommentcreated(now);

		// User submitted info is complete, so let's validate
		boolean commentValid = true;

		// This business of catching validation issues is not good, but it's the iscreen approach
		try {
			// TODO: right now, we only see that the date field is not null (since we check format above), we should have a better date validator
			// TODO: if the user submits a non-double value, what happens when we try to cast it as a double above?
			commentValidator.validate(comment);
		} catch (ValidationException e) {
			commentValid = false;
			log.debug("comment submission did not validate");
		}

		if (commentValid) {
			log.debug("it appears as is if the submitted comment is valid.");
			dao.saveComment(comment);
			luceneIndexer.indexComment(comment);

			return "home";
		}
		else {
			// TODO alert user that comment wasn't saved
			return "home";
		}
	}	
}